#include "sys_TPAdc.h"
#include "sys_types.h"
#include "sys_uart.h"
#include "sys_interrupt.h"
#include "sys_delay.h"
#include "sys_gpio.h"
#include "sys_io.h"
#include "sys_timer.h"

/*寄存器地址*/
#define F1C100S_TPADC_BASE  (0x01C24800)

#define TP_CTRL_REG0  				F1C100S_TPADC_BASE+(0x00)  //TP Control Register 0
#define TP_CTRL_REG1  				F1C100S_TPADC_BASE+(0x04)  //TP Control Register 1
#define TP_CTRL_REG2  				F1C100S_TPADC_BASE+(0x08)  //TP Control Register 2
#define TP_CTRL_REG3 					F1C100S_TPADC_BASE+(0x0C)  //TP Control Register 3
#define TP_INT_FIFO_CTRL_REG  F1C100S_TPADC_BASE+(0x10)  //TP Interrupt FIFO Control Register
#define TP_INT_FIFO_STAT_REG  F1C100S_TPADC_BASE+(0x14)  //TP Interrupt FIFO Status Register
#define TP_COM_DATA_REG  			F1C100S_TPADC_BASE+(0x1C)  //TP Common Data Register
#define TP_DATA_REG  					F1C100S_TPADC_BASE+(0x24)  //TP Data Register
//ADC模式变换顺序为 [X1->X2->Y1->Y2] 32位FIFO连续存储
#define ADC_X1   1				
#define ADC_X2   2		
#define ADC_Y1   4				
#define ADC_Y2   8		
#define ADC_all  0xf

#define TP_MODE   0				
#define ADC_MODE  1

struct tp
{
	int status; //1=按下 0抬起 
	int x;
	int y;
};
struct tp tps;
/*
TP 中断
*/
//int ix,iy;
void IRQ_Touch_Panel_ISR(void)
{

unsigned int reg=0,i,n;
	reg=read32(TP_INT_FIFO_STAT_REG);
/*按下*/
	if(reg&(1<<0))
	{				
		S_BIT(TP_INT_FIFO_STAT_REG,0);
		tps.status=1;
	}
/*抬起*/
	if(reg&(1<<1))	
	{
		S_BIT(TP_INT_FIFO_STAT_REG,1);
		S_BIT(TP_INT_FIFO_CTRL_REG,4);		
		tps.status=0;
		tps.x=0;
		tps.y=0;
	}	
/*FIFO 数据有效中断*/		
	if(reg&(1<<16))
	{
		S_BIT(TP_INT_FIFO_STAT_REG,16);
		n=((reg>>8)&0x1f)/2;
		for(i=0;i<n;i++)
		{
			tps.x=(read32(TP_DATA_REG)&0xfff);
			tps.y=(read32(TP_DATA_REG)&0xfff);
		}			
	}
}

/*
TP ADC 配置IO
*/
void Init_TPADC_IO(void)
{
	GPIO_Congif(GPIOA,GPIO_Pin_0,GPIO_Mode_010,GPIO_PuPd_NOPULL);	
	GPIO_Congif(GPIOA,GPIO_Pin_1,GPIO_Mode_010,GPIO_PuPd_NOPULL);
	GPIO_Congif(GPIOA,GPIO_Pin_2,GPIO_Mode_010,GPIO_PuPd_NOPULL);
	GPIO_Congif(GPIOA,GPIO_Pin_3,GPIO_Mode_010,GPIO_PuPd_NOPULL);	
}
/*TP ADC 初始化
mode =0 TP模式
mode =1 ADC模式
*/
void Init_TP_ADC(int mode)
{
  /*配置IO*/	
	Init_TPADC_IO();
	/*24M / 6 = 4Mhz(CLK_IN)/ 2^13(8192) = 488.28125 hz*/
	/*Conversion Time = 1 / (4MHz/13Cycles) = 3.25us*/
	/*触摸ADC获取时间T_ACQ  = CLK_IN /(16*(1+63)) = 3906.25hz 左右*/		
	write32(TP_CTRL_REG0, (0x3 << 20)  |(0x1f << 23)  | (0x7 << 16)  |  63);		

	/*模式设置*/	
	write32(TP_CTRL_REG1,(5<<12) | (1<< 9));	
	if(mode==ADC_MODE)
		S_BIT(TP_CTRL_REG1,4);//ADC
	else 
		C_BIT(TP_CTRL_REG1,4);//TP
	
	
	write32(TP_CTRL_REG2,((u64_t)0x08 << 28) | (0x0 << 26) | (0 << 24)|0xFFF);
	
/*FIFO触发等级*/
	write32(TP_INT_FIFO_CTRL_REG,(read32(TP_INT_FIFO_CTRL_REG)&(~((0x1f)<<8))) | (0x2)<<8);
	
/*滤波设置*/
	write32(TP_CTRL_REG3,read32(TP_CTRL_REG3) | (1)<<2 | (3)<<0 );
/*FOFO DATA 中断*/	
	if(mode==TP_MODE)
	{
		S_BIT(TP_INT_FIFO_CTRL_REG,0);//按下中断
		S_BIT(TP_INT_FIFO_CTRL_REG,1);//抬起中断		
		S_BIT(TP_INT_FIFO_CTRL_REG,16);//数据中断
		IRQ_Init(IRQ_LEVEL_1,IRQ_Touch_Panel,IRQ_Touch_Panel_ISR ,3);
		sysSetLocalInterrupt(ENABLE_IRQ);//开IRQ中断
	}
/*使能ADC*/	
	S_BIT(TP_CTRL_REG1,5);
}


/*设置ADC通道*/
void Set_ADC_Channel(int Channel)
{
	C_Vlue(TP_CTRL_REG1,0,0xf);	
	S_Vlue(TP_CTRL_REG1,0,Channel);	
}

/*读出AD值*/
int TP_ADC_Read_Value(void)
{
	return (read32(TP_DATA_REG)&0xfff);
}

//——————————————————————————————————————————————————————————————————
//冒泡排序 
void maopao(unsigned int a[],unsigned char n)  
{
	unsigned char i,j;  
    for(i=0;i<n-1;i++)  
        for(j=0;j<n-i-1;j++)  
            if(a[j]>a[j+1])  
            {  
                int t=a[j];  
                a[j]=a[j+1];  
                a[j+1]=t;  
            }  
}



/*TP模式 测试*/
void TP_MODE_Demo(void)	
{
	u32 as=0;
	unsigned int n;
	sysprintf("TP Test...\r\n");
	Init_TP_ADC(TP_MODE);	
	Set_ADC_Channel(ADC_all);
	while(1)
	{
		as=read32(TP_INT_FIFO_STAT_REG);	
		if(as&0x1)//按下
		{
			//sysprintf("TP_CTRL_REG0=0x%08x\r\n",as);
			//sysprintf("TP DOWN...\r\n");					
			S_BIT(TP_INT_FIFO_STAT_REG,0);
			tps.status=1;
		}
		if(as&0x2)//抬起	
		{
			//sysprintf("TP_CTRL_REG0=0x%08x\r\n",as);
			//sysprintf("TP UP...\r\n");
			S_BIT(TP_INT_FIFO_STAT_REG,1);		
			tps.status=2;
		}
    if(tps.status==1)//按下后读AD值
		{
			n=(as>>8)&0x1f;//数据计数
			if(n>=2)
			{
				tps.x=TP_ADC_Read_Value();
				tps.y=TP_ADC_Read_Value();
				sysprintf("TP:n=%d x=%d y=%d \r\n",n,tps.x,tps.y);
			}	
		}
	}
}


/*ADC模式 测试*/
void ADC_MODE_Demo(void)	
{
int key_vl[9]={24,360,700,1000,1380,1710,2040,2400,2740};
unsigned int i=0,_x1,_x2,_y1,_y2,x1[8],x2[8],y1[8],y2[8],x1_key_f=0,x2_key_f=0;
	Init_TP_ADC(ADC_MODE);
	Set_ADC_Channel(ADC_all);
	sysprintf("TP_CTRL_REG0=0x%08x\r\n",read32(TP_CTRL_REG0));
	sysprintf("TP_CTRL_REG1=0x%08x\r\n",read32(TP_CTRL_REG1));	
	sysprintf("TP_CTRL_REG2=0x%08x\r\n",read32(TP_CTRL_REG2));
	sysprintf("TP_CTRL_REG3=0x%08x\r\n",read32(TP_CTRL_REG3));	
	while(1)
	{
		//等待FIFO满
		i=Read_time_ms();
		while(!(read32(TP_INT_FIFO_STAT_REG)&(1<<17)));
		S_BIT(TP_INT_FIFO_STAT_REG,17);
//		sysprintf("Time=%d us\r\n",Read_time_ms()-i);
		//读出
		for(i=0;i<8;i++)
		{
			x1[i]=TP_ADC_Read_Value();
			x2[i]=TP_ADC_Read_Value();
			y1[i]=TP_ADC_Read_Value();
			y2[i]=TP_ADC_Read_Value();
		}
	
		//【排序-中值-平均】
		maopao(x1,8);
		maopao(x2,8);
		maopao(y1,8);
		maopao(y2,8);
		_x1=0;_x2=0,_y1=0,_y2=0;
		for(i=0;i<4;i++)
		{
			_x1+=x1[2+i];
			_x2+=x2[2+i];
			_y1+=y1[2+i];
			_y2+=y2[2+i];
		}
    _x1/=4;
    _x2/=4;		
    _y1/=4;
    _y2/=4;
		//
//		sysprintf("x1=%d\r\n",_x1);
//		sysprintf("x2=%d\r\n",_x2);
//		sysprintf("y1=%d\r\n",_y1);
//		sysprintf("y2=%d\r\n",_y2);	
		/*x1-按键处理*/
		if((_x1<3000)&&(x1_key_f==0))
		{
			x1_key_f=1;
		}
		else if((_x1<3000)&&(x1_key_f==1))
		{
			x1_key_f=2;
			
			for(i=0;i<9;i++)
			{
				if((_x1>(key_vl[i]-50)) && (_x1<(key_vl[i]+50))) 
				{
				  sysprintf("X1-KEY DOWN-%d\r\n",i);
					break;
				}
			}
		}else if((_x1>3000)&&(x1_key_f>1))
		{
			sysprintf("X1-KEY UP\r\n\r\n");
			x1_key_f=0;
		}
		/*x2-按键处理*/
		if((_x2<3000)&&(x2_key_f==0))
		{
			x2_key_f=1;
		}
		else if((_x2<3000)&&(x2_key_f==1))
		{
			x2_key_f=2;
			
			for(i=0;i<9;i++)
			{
				if((_x2>(key_vl[i]-50)) && (_x2<(key_vl[i]+50))) 
				{
				  sysprintf("X2-KEY DOWN-%d\r\n",i);
					break;
				}
			}
		}else if((_x2>3000)&&(x2_key_f>1))
		{
			sysprintf("X2-KEY UP\r\n\r\n");
			x2_key_f=0;
		}	
	}
}
/*TP初始化
返回 1按下
返回 0抬起
*/
int TP_Init(void)
{
	sysprintf("TP Init...\r\n");
	Init_TP_ADC(TP_MODE);	
	Set_ADC_Channel(ADC_all);
	return 0;
}
/*TP读
-1返回无效
0 抬起
1 按下
*/
int TP_Read(unsigned short* x, unsigned short* y)
{	
static int f=0xff;//抬起计数
	if(tps.status==1)//按下
	{
		f=0;
		if((tps.x>0)&&(tps.y>0))//正确返回
		{		
			*x=tps.x;
			*y=tps.y;
			return tps.status;			
		}else//数据有误，返回上次的AD值
		{
			return -1;
		}
	}
	else //抬起
	{
		f++;
		if(f>=5)//
		{
			*x=0;
			*y=0;
			return tps.status;
		}else
		{
			return -1;
		}	
	}
}


